//
//  LBReactPatcherDao.m
//  LBReactPatcher
//
//  Created by WuShiHai on 19/5/24.
//  Copyright (c) 2019 Lebbay All rights reserved.
//

#import "LBReactPatcherDao.h"
#import <LBFoundation/LBFoundation.h>

@interface LBReactPatcherDao()

@property (nonatomic, strong, readwrite) LBDatabase *database;

@end

@implementation LBReactPatcherDao

- (instancetype)initWithDatabase:(LBDatabase *)database {
    if (self = [self init]) {
        _database = database;
    }
    return self;
}

- (NSArray<LBReactPatcherModel *> *)selectAll {
    
    NSMutableArray<LBReactPatcherModel *> *results = [@[] mutableCopy];
    [self.database.queue inTransaction:^(FMDatabase *db, BOOL *rollback) {
        NSString *sql = @"select * from patcher where \
        data_flag = 1 and type = 1 and app_type = 1 and state = 1";
        FMResultSet *resultSet= [db executeQuery:sql];
        while ([resultSet next]) {
            LBReactPatcherModel *model = [LBReactPatcherModel yy_modelWithJSON:[resultSet resultDictionary]];
            if (model) {
                [results addObject:model];
            }
        }
        [resultSet close];
    }];
    return results;
}

- (NSArray<LBReactPatcherModel *> *)selectByVersion:(NSString *)appVersion
                                         identifier:(NSString *)identifier
                                        mainVersion:(NSInteger)mainVersion
                                               type:(LBReactPatcherType)type {
    NSMutableArray<LBReactPatcherModel *> *results = [@[] mutableCopy];
    [self.database.queue inTransaction:^(FMDatabase *db, BOOL *rollback) {
        NSString *sql = @"select * from patcher where \
        data_flag = 1 and type = 1 and app_type = 1 and state = 1";
        sql = appVersion.length > 0 ? [NSString stringWithFormat:@"%@ and app_version = '%@'", sql, appVersion] : sql;
        sql = identifier.length > 0 ? [NSString stringWithFormat:@"%@ and app_identifier = '%@'", sql, identifier] : sql;
        sql = mainVersion > 0 ? [NSString stringWithFormat:@"%@ and main_version = %@", sql, @(mainVersion)] : sql;
        sql = type != LBReactPatcherTypeUnknown > 0 ? [NSString stringWithFormat:@"%@ and type = %@", sql, @(type)] : sql;
        sql = [sql stringByAppendingString:@" order by id"];
        FMResultSet *resultSet= [db executeQuery:sql];
        while ([resultSet next]) {
            LBReactPatcherModel *model = [[LBReactPatcherModel alloc] init];
            if ([resultSet resultDictionary]) {
                [model setValueFromSqlReuslt:[resultSet resultDictionary]];
                [results addObject:model];
            }
        }
        [resultSet close];
    }];
    return results;
}

- (NSArray<LBReactPatcherModel *> *)selectByVersion:(NSString *)appVersion
                                         identifier:(NSString *)identifier
                                             isMain:(BOOL)isMain
                                        mainVersion:(NSInteger)mainVersion
                                         moduleName:(NSString *)moduleName
                                               type:(LBReactPatcherType)type {
    NSMutableArray<LBReactPatcherModel *> *results = [@[] mutableCopy];
    [self.database.queue inTransaction:^(FMDatabase *db, BOOL *rollback) {
        NSString *sql = @"select * from patcher where \
        data_flag = 1 and type = 1 and app_type = 1 and state = 1";
        sql = appVersion.length > 0 ? [NSString stringWithFormat:@"%@ and app_version = '%@'", sql, appVersion] : sql;
        sql = identifier.length > 0 ? [NSString stringWithFormat:@"%@ and app_identifier = '%@'", sql, identifier] : sql;
        sql = [NSString stringWithFormat:@"%@ and bundle_type = %@", sql, isMain ? @(1) : @(0)];
        sql = mainVersion > 0 ? [NSString stringWithFormat:@"%@ and main_version = %@", sql, @(mainVersion)] : sql;
        sql = moduleName.length > 0 ? [NSString stringWithFormat:@"%@ and module_name = '%@'", sql, moduleName] : sql;
        sql = type != LBReactPatcherTypeUnknown > 0 ? [NSString stringWithFormat:@"%@ and type = %@", sql, @(type)] : sql;
        sql = [sql stringByAppendingString:@" order by id desc"];
        FMResultSet *resultSet= [db executeQuery:sql];
        while ([resultSet next]) {
            LBReactPatcherModel *model = [[LBReactPatcherModel alloc] init];
            if ([resultSet resultDictionary]) {
                [model setValueFromSqlReuslt:[resultSet resultDictionary]];
                [results addObject:model];
            }
        }
        [resultSet close];
    }];
    return results;
}

- (BOOL)updateState:(LBReactPatcherModel *)model {
    if (model.bundleId <= 0) {
        return NO;
    }
    __block BOOL success = NO;
    [self.database.queue inTransaction:^(FMDatabase *db, BOOL *rollback) {
        NSString *sql = @"update patcher set state = ? where id = ?";
        success = [db executeUpdate:sql,
                   @(model.state),
                   @(model.bundleId)];
        if (!success) {
            *rollback = YES;
        }
    }];
    return success;
}

- (BOOL)delete:(LBReactPatcherModel *)model {
    if (model.bundleId <= 0) {
        return NO;
    }
    __block BOOL success = NO;
    [self.database.queue inTransaction:^(FMDatabase *db, BOOL *rollback) {
        NSString *sql = @"update patcher set data_flag = 0 where id = ";
        success = [db executeUpdate:sql,
                   @(model.bundleId)];
        if (!success) {
            *rollback = YES;
        }
    }];
    return success;
}

- (BOOL)insert:(LBReactPatcherModel *)model {
    if (!model) {
        return NO;
    }
    return [self insertPatchers:@[model]];
}

- (BOOL)insertPatchers:(NSArray<LBReactPatcherModel *> *)patchers {
    __block BOOL success = NO;
    [self.database.queue inTransaction:^(FMDatabase *db, BOOL *rollback) {
        NSString *sql = @"replace into patcher( \
        id, type, app_type, bundle_type, app_identifier, app_version, \
        main_version, module_name, check_code, state, url, data_flag \
        ) values(?,?,?,?,?,?,?,?,?,?,?,?)";
        for (LBReactPatcherModel *model in patchers){
            success = [db executeUpdate:sql,
                       @(model.bundleId),
                       @(model.type),
                       @(model.appType),
                       @(model.bundleType),
                       model.appIdentifier,
                       model.appVersion,
                       @(model.mainVersion),
                       model.moduleName,
                       model.checkCode,
                       @(model.state),
                       model.url,
                       @(1)];
            if (!success) {
                NSLog(self.database.lastError);
                *rollback = YES;
                break;
            }
        }
    }];
    return success;
}


@end
